#include "BaseListeSel.h"

#include "Key.h"

#include "lib.h"
#include "Qlib.h"

#include <QtGui/QGroupBox>
#include <QtGui/QPushButton>
#include <QtGui/QLCDNumber>
#include <QtGui/QCheckBox>
#include <QtGui/QButtonGroup>
#include <QtGui/QGridLayout>

#include <QtGui/QApplication>

using namespace std;

DebugLevelType BaseListeSel::gestionListe( BLANK );

/**
 * Constructeur permettant de créer un choix à partir d'une liste de
 * noms, où les items sont gratuits. Cela sert probablement à choisir
 * une catégorie, le choix sera unique.
 *
 * La liste des noms est ici donnée par un pointeur sur un tableau
 * (supposé statique), alors on copie ses éléments dans la liste
 * interne.
 *
 * Le niveau de sortie est paramétré par BaseUI::interne :\n
 * - \e FUNC  affiche les messages de début et de fin de méthode.\n
 *
 * @param nbr nombre d'objets à choisir.
 * @param ptr pointeur sur le noms des différents éléments.
 * @param titre nom du cadre affiché autour des items.
 * @param nomFenetre nom du Widget (créé automatiquement).
 * @param parent pointeur sur le widget parent (orphelin par défaut).
 */
BaseListeSel::BaseListeSel(const unsigned int& nbr, string* ptr,
			   const string& titre, const string& nomFenetre,
			   QWidget* parent)
  : BaseUI( nomFenetre.c_str(), parent ), dimension( nbr ), PP( 0 ),
    affichePP( false )
{
  /*Debug::*/empileNiveau( &interne );
  func() << "BaseListeSel::BaseListeSel 1 -> début" << endmsg;

  for (unsigned int i(0); i < nbr; i++)
    {
      Liste.push_back( *(ptr + i) );
      debug() << Liste.back() << endmsg;
    }

  etatsTriples.assign(dimension, false);

  aChoisi.assign(dimension, false);

  analyseListe();

  prepareAffichage(titre);

  func() << "BaseListeSel::BaseListeSel -> fin" << endmsg;
  /*Debug::*/depileNiveau();
}

/**
 * Constructeur permettant de créer un choix à partir d'une liste de
 * noms, où les items sont gratuits. Cela sert probablement à choisir
 * une catégorie, le choix sera unique.
 *
 * La liste des noms est ici donnée par un pointeur sur un tableau
 * (supposé statique), alors on copie ses éléments dans la liste
 * interne.
 *
 * Le niveau de sortie est paramétré par BaseUI::interne :\n
 * - \e FUNC  affiche les messages de début et de fin de méthode.\n
 *
 * @param nbr nombre d'objets à choisir.
 * @param ptr pointeur sur le noms des différents éléments. Attention
 * ici c'est un pointeur sur un élément constant du tableau!
 * @param titre nom du cadre affiché autour des items.
 * @param nomFenetre nom du Widget (créé automatiquement).
 * @param parent pointeur sur le widget parent (orphelin par défaut).
 */
BaseListeSel::BaseListeSel(const unsigned int& nbr, const string* ptr,
			   const string& titre, const string& nomFenetre,
			   QWidget* parent)
  : BaseUI( nomFenetre.c_str(), parent ), dimension( nbr ), PP( 0 ),
    affichePP( false )
{
  /*Debug::*/empileNiveau( &interne );
  func() << "BaseListeSel::BaseListeSel 2 -> début" << endmsg;

  for (unsigned int i(0); i < dimension; i++)
    {
      Liste.push_back( *(ptr + i) );
      debug() << Liste.back() << endmsg;
    }

  etatsTriples.assign(dimension, false);

  aChoisi.assign(dimension, false);

  analyseListe();

  prepareAffichage(titre);

  fenetreLayout -> addWidget(boite);

  func() << "BaseListeSel::BaseListeSel -> fin" << endmsg;
  /*Debug::*/depileNiveau();
}

/**
 * Constructeur permettant de créer un choix à partir d'une liste de
 * noms, où les items sont gratuits. Cela sert probablement à choisir
 * une catégorie, le choix sera unique.
 *
 * Le niveau de sortie est paramétré par BaseUI::interne :\n
 * - \e FUNC  affiche les messages de début et de fin de méthode.\n
 *
 * @param nbr nombre d'objets à choisir.
 * @param noms pointeur sur le conteneur des noms.
 * @param titre nom du cadre affiché autour des items.
 * @param nomFenetre nom du Widget (créé automatiquement).
 * @param parent pointeur sur le widget parent (orphelin par défaut).
 */
BaseListeSel::BaseListeSel(const unsigned int& nbr, 
			   const vector< string >* noms, const string& titre,
			   const string& nomFenetre, QWidget* parent)
  : BaseUI( nomFenetre.c_str(), parent ), dimension( nbr ), PP( 0 ),
    affichePP( false )
{
  /*Debug::*/empileNiveau( &interne );
  func() << "BaseListeSel::BaseListeSel 3 -> début" << endmsg;

  Liste.assign(noms -> begin(), noms -> end());

  etatsTriples.assign(dimension, false);

  aChoisi.assign(dimension, false);

  analyseListe();

  prepareAffichage(titre);

  fenetreLayout -> addWidget(boite);

  func() << "BaseListeSel::BaseListeSel -> fin" << endmsg;
  /*Debug::*/depileNiveau();
}

/**
 * Constructeur permettant de créer un choix à partir d'une liste de
 * noms, où les items ont un coût, également donné en argument. Ce
 * constructeur est utilisé pour le choix de compétences diverses,
 * dons et désavantages par exemple.
 *
 * La liste des noms et celle des coûts sont ici données par un
 * pointeur sur un tableau (supposé statique), alors on copie leurs
 * éléments dans les listes internes.
 *
 * Le niveau de sortie est paramétré par BaseUI::interne :\n
 * - \e FUNC  affiche les messages de début et de fin de méthode.\n
 *
 * @param nbr nombre d'objets à choisir.
 * @param ptr pointeur sur le noms des différents éléments.
 * @param ptr_cout pointeur sur le premier des coûts.
 * @param pp nombre de pp pouvant être dépensés.
 * @param titre nom du cadre affiché autour des items.
 * @param nomFenetre nom du Widget (créé automatiquement).
 * @param parent pointeur sur le widget parent (orphelin par défaut).
 */
BaseListeSel::BaseListeSel(const unsigned int& nbr, string* ptr,
			   int* ptr_cout, const unsigned int& pp,
			   const string& titre, const string& nomFenetre,
			   QWidget* parent)
  : BaseUI( nomFenetre.c_str(), parent ), dimension( nbr ), PP( pp ),
    affichePP( true )
{
  /*Debug::*/empileNiveau( &interne );
  func() << "BaseListeSel::BaseListeSel 4 -> début" << endmsg;

  for (unsigned int i(0); i < nbr; i++)
    {
      Liste.push_back( *(ptr + i) );
      Couts.push_back( *(ptr_cout + i) );
      debug() << Liste.back()  << " - " << Couts.back() << endmsg;
    }

  etatsTriples.assign(dimension, false);

  aChoisi.assign(dimension, false);

  analyseListe();

  prepareAffichage(titre);

  nbrPP = new QLCDNumber(this);
  nbrPP -> setSegmentStyle(QLCDNumber::Flat);
  nbrPP -> display(PP);

  fenetreLayout -> addWidget(nbrPP);
  fenetreLayout -> addWidget(boite);

  func() << "BaseListeSel::BaseListeSel -> fin" << endmsg;
  /*Debug::*/depileNiveau();
}

/**
 * Constructeur permettant de créer un choix à partir d'une liste de
 * noms, où les items ont un coût, également donné en argument. Ce
 * constructeur est utilisé pour le choix de compétences diverses,
 * dons et désavantages par exemple.
 *
 * La liste des noms et celle des coûts sont ici données par un
 * pointeur sur un tableau (supposé statique), alors on copie leurs
 * éléments dans les listes internes.
 *
 * Le niveau de sortie est paramétré par BaseUI::interne :\n
 * - \e FUNC  affiche les messages de début et de fin de méthode.\n
 *
 * @param nbr nombre d'objets à choisir.
 * @param ptr pointeur sur le noms des différents éléments. Attention
 * ici c'est un pointeur sur un élément constant du tableau!
 * @param ptr_cout pointeur sur le premier des coûts.
 * @param pp nombre de pp pouvant être dépensés.
 * @param titre nom du cadre affiché autour des items.
 * @param nomFenetre nom du Widget (créé automatiquement).
 * @param parent pointeur sur le widget parent (orphelin par défaut).
 */
BaseListeSel::BaseListeSel(const unsigned int& nbr, const string* ptr,
			   int* ptr_cout, const unsigned int& pp,
			   const string& titre, const string& nomFenetre,
			   QWidget* parent)
  : BaseUI( nomFenetre.c_str(), parent ), dimension( nbr ), PP( pp ),
    affichePP( true )
{
  /*Debug::*/empileNiveau( &interne );
  func() << "BaseListeSel::BaseListeSel 5 -> début" << endmsg;

  for (unsigned int i(0); i < nbr; i++)
    {
      Liste.push_back( *(ptr + i) );
      Couts.push_back( *(ptr_cout + i) );
      debug() << Liste.back() << " - " << Couts.back() << endmsg;
    }

  etatsTriples.assign(dimension, false);

  aChoisi.assign(dimension, false);

  analyseListe();

  prepareAffichage(titre);

  nbrPP = new QLCDNumber(this);
  nbrPP -> setSegmentStyle(QLCDNumber::Flat);
  nbrPP -> display(PP);

  fenetreLayout -> addWidget(nbrPP);
  fenetreLayout -> addWidget(boite);

  prepareBoutons();

  func() << "BaseListeSel::BaseListeSel -> fin" << endmsg;
  /*Debug::*/depileNiveau();
}

/**
 * Constructeur permettant de créer un choix à partir d'une liste de
 * noms, où les items ont un coût, également donné en argument. Ce
 * constructeur est utilisé pour le choix de compétences diverses,
 * dons et désavantages par exemple.
 *
 * Le niveau de sortie est paramétré par BaseUI::interne :\n
 * - \e FUNC  affiche les messages de début et de fin de méthode.\n
 *
 * @param nbr nombre d'objets à choisir.
 * @param noms pointeur sur le conteneur des noms des différents
 * éléments. Attention ici c'est un pointeur sur un tableau constant!
 * @param couts pointeur sur le conteneur des coûts des différents
 * éléments. Attention ici c'est un pointeur sur un tableau constant!
 * @param pp nombre de pp pouvant être dépensés.
 * @param titre nom du cadre affiché autour des items.
 * @param nomFenetre nom du Widget (créé automatiquement).
 * @param parent pointeur sur le widget parent (orphelin par défaut).
 */
BaseListeSel::BaseListeSel(const unsigned int& nbr,
			   const vector< string >* noms,
			   const vector< unsigned int >* couts,
			   const unsigned int& pp, const string& titre,
			   const string& nomFenetre, QWidget* parent)
  : BaseUI( nomFenetre.c_str(), parent ), dimension( nbr ), PP( pp ),
    affichePP( false )
{
  /*Debug::*/empileNiveau( &interne );
  func() << "BaseListeSel::BaseListeSel 6 -> début" << endmsg;

  Liste.assign(noms -> begin(), noms -> end());
  Couts.assign(couts -> begin(), couts -> end());

  etatsTriples.assign(dimension, false);

  aChoisi.assign(dimension, false);

  analyseListe();

  prepareAffichage(titre);

  fenetreLayout -> addWidget(boite);

  func() << "BaseListeSel::BaseListeSel -> fin" << endmsg;
  /*Debug::*/depileNiveau();
}

/**
 * Constructeur de copie. On copie la liste de strings et de coûts,
 * ainsi que la liste des éventuels coix déjà effectués. Il faut
 * encore récupérer le titre du groupe de boutons.
 *
 * @param listeSel instance de BaseListeSel à dupliquer.
 */
BaseListeSel::BaseListeSel(const BaseListeSel& listeSel)
  : BaseUI( listeSel ), dimension( listeSel.dimension ),
    PP( listeSel.PP ), affichePP( listeSel.affichePP )
{
  Liste.assign( listeSel.Liste.begin(), listeSel.Liste.end() );
  Couts.assign( listeSel.Couts.begin(), listeSel.Couts.end() );
  
  etatsTriples.assign(dimension, false);
  
  aChoisi.assign( listeSel.aChoisi.begin(), listeSel.aChoisi.end() );
  
  analyseListe();
  
  prepareAffichage( listeSel.boite -> title() . toStdString() );
  
  fenetreLayout -> addWidget(boite);  
}

/**
 * Destructeur, ne fait rien de spécial. Est déclaré virtual pour
 * assurer une destruction propre des objets dérivés.
 */
BaseListeSel::~BaseListeSel()
{}

/** Affiche la fenêtre et permet d'effectuer le choix dans liste.
 * Une fois le choix validé, on rempli le conteneur avec les items
 * sélectionnés.
 *
 * @param vec conteneur de la liste des éléments choisis.
 * @return StatusCode \e true si choix validé, \e false sinon.
 */
StatusCode BaseListeSel::Choisir(vector< unsigned int >& vec)
{
  vec.clear();

  this -> show();

  qApp -> exec();

  if ( OK )
    {
      for (unsigned int i(0); i < dimension; i++)
	{
	  if (aChoisi[i])
	    vec.push_back(i);
	}
    }

  return StatusCode( OK );
}

/**
 * Permet de modifier la valeur de BaseListeSel::gestionListe.
 *
 * @param level nouvelle valeur de  BaseListeSel::gestionListe.
 */
void BaseListeSel::setLevel(const DebugLevelType& level)
{
  gestionListe = level;
}

/**
 * Crée la liste des QCheckBox permettant de sélectionner les
 * différents items. Regarde dans BaseListeSel::mapEtatsTriples pour
 * savoir si un bouton trinaire est nécessaire. Si oui, le nom affiché
 * dépend de l'état de bouton.
 *
 * Le niveau de sortie est paramétré par BaseUI::interne :\n
 * - \e FUNC  affiche les messages de début et de fin de méthode.\n
 * - \e LFUNC affiche un message lorsqu'un bouton trinaire est
 * nécessaire.\n
 * - \e DEBUG affiche un message pour l'ajout d'un bouton
 * conventionnel.\n
 *
 * @param titre nom du groupe.
 */
void BaseListeSel::prepareAffichage(const string& titre)
{
  /*Debug::*/empileNiveau( &interne );
  func() << "BaseListeSel::prepareAffichage -> début" << endmsg;

  boite = new QGroupBox( QString::fromUtf8( titre.c_str() ), this );
  QGridLayout *boiteLayout = new QGridLayout;

  groupe = new QButtonGroup( this );

  groupe -> setExclusive( !affichePP );

  map<Key, unsigned int>::const_iterator it, Begin(mapEtatsTriples.begin()),
    End(mapEtatsTriples.end());

  unsigned int pos, num;

  string tmpStr;

  for (it = Begin; it != End; it++)
    {
      num = it -> second;
      pos = it -> first.Nombre;
      QCheckBox *tmpBouton;
      if ( it -> first.Etat == 1) // Il nous faut un tristate!
	{
	  tmpStr = Liste[num];
	  tmpStr = tmpStr.substr(0, tmpStr.find("(") - 1 );
	  lfunc() << "Un tristate pour " << Liste[num] << " -> "
		  << tmpStr << endmsg;
       	  tmpBouton = new QCheckBox( trUtf8( tmpStr.c_str() ), this );
	  tmpBouton -> setTristate( true );
	  groupe -> addButton(tmpBouton, pos);
	  it++;
	}
      else	
	groupe ->
	  addButton(new QCheckBox( trUtf8( Liste[num].c_str() ), this ),
		    pos);
      boiteLayout -> addWidget(groupe -> button(pos), pos % 10, pos / 10 );
      debug() << "Ajout du bouton "
	      << toUtf8StdString(groupe -> button(pos) -> text()) << endmsg;
    }

  boite -> setLayout(boiteLayout);

  connect(groupe, SIGNAL(buttonClicked(int)), this, SLOT(ajout(int)));

  func() << "BaseListeSel::prepareAffichage -> fin" << endmsg;
  /*Debug::*/depileNiveau();
}

/**
 * Ajoute les boutons "OK" et "Annuler" à BaseUI::boutons. Cette
 * méthode permet d'éviter d'avoir ces 6 lignes présentes dans les 6
 * différents constructeurs.
 */
void BaseListeSel::prepareBoutons()
{
  boutons.push_back( new QPushButton( trUtf8("&Quitter"), this ) );
  boutons.back() -> setToolTip( trUtf8("Quitter le programme") );
  connect( boutons.back()  , SIGNAL( clicked() ), this, SLOT( annuler() ) );

  boutons.push_back( new QPushButton( trUtf8("&OK"), this ) );
  boutons.back() -> setToolTip( trUtf8("Accepter et continuer") );
  connect( boutons.back(), SIGNAL( clicked() ), this, SLOT( fermer() ) );
}

/**
 * Analyse la liste de noms pour identifier des paire d'items
 * semblables comme Lâcheté (modérée) et Lâcheté (grave). La détection
 * de telles paires repose sur la syntaxe particulière de tels
 * éléments : on attend un même nom si on exclu le contenu de la
 * parenthèse.
 *
 * L'information est ensuite écrite dans le conteneur associatif
 * mapEtatsTriples : il faut relier le numéro du bouton à l' (aux)
 * item(s) correspondant. Pour un bouton conventionnel, la clé du
 * conteneur est (numéro, 0) et la valeur associée est le numéro de
 * l'item dans la liste Liste. Pour un bouton trinaire, il y a deux
 * clés : (numéro, 1) et (numéro, 2) dont les valeurs associées sont
 * les deux différents index de Liste.
 *
 * Le niveau de sortie est paramétré par BaseListeSel::gestionListe :\n
 * - \e FUNC affiche les messages de début et de fin de méthode.\n
 * - \e LINFO affiche pour chaque index i de Liste le numéro du
 * bouton, la clé et l'éventuel coût.
 */
void BaseListeSel::analyseListe()
{
  /*Debug::*/empileNiveau( &gestionListe );
  func() << "BaseListeSel::analyseListe -> début" << endmsg;

  unsigned int i, j, compteur(0);

  size_t loc;

  for (i = 0; i < dimension; i++)
    {
      loc = Liste[i].find("(");
      if ( loc == string::npos )
	{
	  Key clef(compteur, 0);
	  mapEtatsTriples. insert ( pair<Key, unsigned int>( clef , i ) );
 	  linfo() << "élément " << i << " =>  bouton " << compteur
		  << " clé " << clef.Nombre << " " << clef.Etat
		  << " pour " << Liste[i];
	  if ( !Couts.empty() )
	    linfo() << " couts " << Couts[i];
	  linfo() << endmsg;
	  compteur++;
	  continue;
	}
      for (j = i + 1; j < dimension; j++)
	{
	  if ( Liste[j].find("(") == loc)
	    {
	      if ( Liste[i].substr(0, loc) == 
		   Liste[j].substr(0, loc)
		   )
		{
		  etatsTriples[i] = true;
		  etatsTriples[j] = true;
		  if ( Couts[i] > Couts[j] )
		    {
		      Key clef1(compteur, 1);
		      Key clef2(compteur, 2);
		      mapEtatsTriples[clef1] = i;
		      mapEtatsTriples[clef2] = j;
		      linfo() << "éléments " << i << ", " << j << " => bouton"
			      << compteur << " clés" << clef1.Nombre << " "
			      << clef1.Etat << " ,  " << clef2.Nombre << " "
			      << clef2.Etat << " pour " << Liste[i] << " , "
			      << Liste[j];
		    }
		  else
		    {
		      Key clef1(compteur, 1);
		      Key clef2(compteur, 2);
		      mapEtatsTriples[clef1] = j;
		      mapEtatsTriples[clef2] = i;
		      linfo() << "éléments " << i << ", " << j << " => bouton"
			      << compteur << " clés" << clef1.Nombre << " "
			      << clef1.Etat << " ,  " << clef2.Nombre << " "
			      << clef2.Etat << " pour " << Liste[i] << " , "
			      << Liste[j];
		    }
		  if ( !Couts.empty() )
		    linfo() << " couts " << Couts[i] << ", " << Couts[j];
		  linfo() << endmsg;
		  compteur++;
		}
	      else if (j == dimension - 1)
		{
		  Key clef(compteur, 0);
		  mapEtatsTriples[clef] = j;
		  linfo() << "élément " << i << " =>  bouton " << compteur
			  << " clé " << clef.Nombre << " " << clef.Etat
			  << " pour " << Liste[i];
		  if ( !Couts.empty() )
		    linfo() << " couts " << Couts[i];
		  linfo() << endmsg;
		  compteur++;
		}
	    }
	}
    }

  func() << "BaseListeSel::analyseListe -> fin" << endmsg;
  /*Debug::*/depileNiveau();
}

/**
 * Gère la sélection et la suppression des différents items. Un coût
 * nul indique ici que l'on ne peut choisir qu'un élément (choix
 * exclusif).
 *
 * Les boutons trinaires doivent être traités avec un soin particulier
 * : il faut savoir dans quel état ils sont, afin de déterminer
 * correctement le coût appliqué, l'affichage est en outre modifié.
 *
 * Pour un bouton trinaire, on récupère l'état (0, 1 ou 2), et on sait
 * grâce à mapEtatsTriples quelle item a été sélectionnée (ou
 * supprimé). Le coût est calculé (en faisant attention lors du
 * passage de l'état 1 $ l'état 2).
 *
 * Le niveau de sortie est paramétré par BaseUI::interne :\n
 * - \e FUNC affiche les messages de début et de fin de méthode.\n
 * - \e LINFO affiche quel est l'item sélectionné (ou supprimé) pour un
 * bouton trinaire, ou l'ensemble numéro de bouton, clé, item pour un
 * bouton conventionnel.\n
 * - \e DEBUG affiche la catégorie (dé)sélectionnée et l'éventuel coût
 * appliqué.
 *
 * @param i numéro du bouton actionné.
 */
void BaseListeSel::ajout(const int& i)
{
  /*Debug::*/empileNiveau( &interne );
  func() << "BaseListeSel::ajout -> début" << endmsg;

  if ( Couts.empty() )
    {
      if ( groupe -> button(i) -> isChecked() )
	{
	  aChoisi[i] = true;
	  debug() << "Sélection de la catégorie " << Liste[i] << endmsg;
	}
      else
	{
	  aChoisi[i] = false;
	  debug() << "Désélection de la catégorie " << Liste[i] << endmsg;
	}
    }
  else
    {
      int cout(0);
      unsigned int pos;
      string tmpStr;
      if ( static_cast<QCheckBox*>(groupe -> button(i)) -> isTristate() )
	{
	  unsigned int etat(static_cast<QCheckBox*>(groupe -> button(i)) -> checkState());
	  debug() << "Etat " << etat << endmsg;
	  Key clef1(static_cast<unsigned int>(i), 1);
	  Key clef2(static_cast<unsigned int>(i), 2);
	  switch(etat)
	    {
	    case 0:
	      // On passe de très cher à rien
	      cout = - Couts[mapEtatsTriples[clef2]];
	      aChoisi[mapEtatsTriples[clef2]] = false;
	      tmpStr = Liste[mapEtatsTriples[clef2]];
	      tmpStr = tmpStr.substr(0, tmpStr.find("(") - 1 );
	      groupe -> button(i) -> setText( QString::fromUtf8(tmpStr.c_str()) );
	      linfo() << "On supprime " << tmpStr << endmsg;
	      break;
	    case 1:
	      cout = Couts[mapEtatsTriples[clef1]];
	      aChoisi[mapEtatsTriples[clef1]] = true;
	      groupe -> button(i) -> setText( QString::fromUtf8(Liste[mapEtatsTriples[clef1]].c_str()) );
	      linfo() << "On passe à " << Liste[mapEtatsTriples[clef1]]
		      << endmsg;
	      break;
	    case 2:
	      cout = Couts[mapEtatsTriples[clef2]] -
		Couts[mapEtatsTriples[clef1]];
	      aChoisi[mapEtatsTriples[clef1]] = false;
	      aChoisi[mapEtatsTriples[clef2]] = true;
	      groupe -> button(i) -> setText( QString::fromUtf8(Liste[mapEtatsTriples[clef2]].c_str()) );
	      linfo() << "On passe à " << Liste[mapEtatsTriples[clef2]]
		      << endmsg;
	      break;
	    default:
	      warning() << "Ne sais pas quoi faire avec " << etat << endmsg;
	    }
	  PP -= cout;
	}
      else
	{
	  Key clef(i);
	  pos = mapEtatsTriples[clef];
	  cout = Couts[pos];
	  linfo() << "élément " << pos << " =>  bouton " << i
		  << " clé " << clef.Nombre << " " << clef.Etat
		  << " pour " << Liste[pos]
		  << " cout " << Couts[pos] << endmsg;
	  if (groupe -> button(i) -> isChecked())
	    {
	      PP -= cout;
	      aChoisi[pos] = true;
	    }
	  else
	    {
	      PP += cout;
	      aChoisi[pos] = false;
	    }
	}
      debug() << "Cout appliqué " << cout << endmsg;
      nbrPP -> display(PP);
    }

  func() << "BaseListeSel::ajout -> fin" << endmsg;
  /*Debug::*/depileNiveau();
}

/**
 * Redéfinition de BaseUI::fermer, afin de garantir que l'on a pas
 * sélectionné trop d'item en rapport avec le nombre de PP
 * disponibles.
 */
void BaseListeSel::fermer()
{
  OK = true;

  if (PP < 0)
    return;

  close();
}
